home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
ftp.mactech.com 2010
/
ftp.mactech.com.tar
/
ftp.mactech.com
/
machack
/
Hacks95
/
MacsBugTV.sit
/
MacsBug TV
/
Sources
/
MTVdcmd.c
next >
Wrap
Text File
|
1995-06-24
|
29KB
|
1,059 lines
/*
File: MTVdcmd.c
Contains: MacsBug TV debugger command
Written by: Chris Wysocki
Copyright: © 1995 Christopher R. Wysocki. All rights reserved.
Change History (most recent first):
6/24/95 crw Added top and left options
6/22/95 crw Got it finally working
5/20/95 crw New today
Notes:
- requires Quadra/Power Mac AV video card (Civic)
*/
//====================================================================================================
// Includes
//====================================================================================================
#if applec && mc68000
#pragma load "MTVdcmd.dump"
#endif
#define SystemSevenOrLater 1
#include <Types.h>
#include <Devices.h>
#include <Gestalt.h>
#include <LowMem.h>
#include <Memory.h>
#include <TextUtils.h>
#include <PLStringFuncs.h>
#include "dcmd.h"
#include "put.h"
#undef Version3dcmd
#include "MTVdcmd.h"
//====================================================================================================
// Constants
//====================================================================================================
#define kMacsBugMaxWidth 640 // maximum width of MacsBug display
#define kMacsBugMaxHeight 480 // maximum height of MacsBug display
#define kDefaultVideoWidth 160 // default width of video display
#define kDefaultVideoHeight 120 // default height of video display
#define kMinimumVideoWidth 0 // minimum width of video display
#define kMinimumVideoHeight 0 // minimum height of video display
#define kMaximumVideoWidth 640 // maximum width of video display
#define kMaximumVideoHeight 480 // maximum height of video display
#define kDcmdVersion ((kDcmdMajorVersion << 24L) | \
(kDcmdMinorVersion << 16L) | \
(kDcmdStage << 8L) | \
(kDcmdNonRelRev))
#define kDcmdNameStr "MTV"
#define kDcmdUsageStr "option [option…]"
#define kDcmdCreditsStr "Chris Wysocki/MacHack 1995 - built " __DATE__ " at " __TIME__
#define kCivic68KBaseAddr 0x50036000 // Civic base address
#define kSebas68KAddrReg 0x50F30000 // Sebastian address register
#define kSebas68KDataReg 0x50F30010 // Sebastian data register
#define kSebas68KCLUT 0x50F30020 // Sebastian color lookup table
#define kCivicPPCBaseAddr 0xE0036000 // Civic base address
#define kSebasPPCAddrReg 0xE0F30000 // Sebastian address register
#define kSebasPPCDataReg 0xE0F30010 // Sebastian data register
#define kSebasPPCCLUT 0xE0F30020 // Sebastian color lookup table
#define csCivicSetVidInRect 138 // Control csCode for Civic video driver
enum { // error result codes
errMTVSyntaxError = -10000, // command syntax error
errMTVUnknownOption = -10001, // unknown command line option
errMTVFeatureNotImplemented = -10002, // specified feature is not implemented
errMTVHardwareNotAvailable = -10003, // required hardware is not available
errMTVValueOutOfRange = -10004 // specified value is out of range
};
//====================================================================================================
// Type Definitions
//====================================================================================================
struct VDVidInRect // for csCivicSetVidInRect to Civic video driver
{
Rect csRect; // set to playthrough rectangle in global coordinates
short csPage; // always 0
long csBaseAddr; // always $98765432 (ignored?)
};
typedef struct VDVidInRect VDVidInRect;
struct CLUTEntry
{
unsigned char red; // red component
unsigned char green; // green component
unsigned char blue; // blue component
unsigned char alpha; // alpha channel
};
typedef struct CLUTEntry CLUTEntry, *CLUTEntryPtr;
//====================================================================================================
// Global Variables
//====================================================================================================
Boolean gIsPowerPC; // true if running on PowerPC
Boolean gHasCivic; // true if Civic video hardware is present
Boolean gHasValkyrie; // true if Valkyrie video hardware is present
Boolean gHasTVTuner; // true if Valkyrie TV tuner is present
Boolean gPlaythroughOn; // true if video playthough is enabled
short gCivicRefNum; // refnum of Civic video driver
short gValkyrieRefNum; // refnum of Valkyrie video driver
Rect gVideoRect; // playthrough rectangle in global coordinates
Ptr gCivicBaseAddr; // base address of Civic chip, if present
Ptr gSebasAddrReg; // address of Sebastian address register, if present
Ptr gSebasDataReg; // address of Sebastian address register, if present
Ptr gSebasCLUT; // address of Sebastian CLUT, if present
//====================================================================================================
// Inline Functions
//====================================================================================================
pascal void NOP(void) = { 0x4E71 };
//====================================================================================================
// Prototypes
//====================================================================================================
static void HandleDcmdInit(dcmdBlock *paramPtr);
static void HandleDcmdSecondaryInit(dcmdBlock *paramPtr);
static void HandleDcmdShutdown(dcmdBlock *paramPtr);
static void HandleDcmdHelp(dcmdBlock *paramPtr);
static void HandleDcmdGetInfo(dcmdBlock *paramPtr);
static void HandleDcmdDoIt(dcmdBlock *paramPtr);
static OSErr TurnVideoOn(void);
static OSErr TurnVideoOff(void);
static OSErr SetVideoSize(long size);
static OSErr SetVideoLeft(long left);
static OSErr SetVideoTop(long top);
static OSErr SetVideoWidth(long width);
static OSErr SetVideoHeight(long height);
static void SetVideoPlaythrough(Boolean on);
static OSErr SetVideoRectangle(const Rect *videoRect);
static OSErr SetTVChannel(long channel);
static OSErr DumpCLUT(void);
static void ReadCivicCLUTEntry(unsigned char index, CLUTEntryPtr entry);
static void WriteCivicCLUTEntry(unsigned char index, const CLUTEntryPtr entry);
static short GetDriverRefNum(const StringPtr driverName);
//====================================================================================================
//
// Routine: CommandEntry
//
// Description: Main entry point for dcmd
//
// Parameters: paramPtr - pointer to dcmd paramter block
//
// Returns: nothing
//
//====================================================================================================
pascal void
CommandEntry(dcmdBlock *paramPtr)
{
switch (paramPtr->request)
{
case dcmdInit:
HandleDcmdInit(paramPtr);
break;
case dcmdSecondaryInit:
HandleDcmdSecondaryInit(paramPtr);
break;
case dcmdShutdown:
HandleDcmdShutdown(paramPtr);
break;
case dcmdHelp:
HandleDcmdHelp(paramPtr);
break;
case dcmdGetInfo:
HandleDcmdGetInfo(paramPtr);
break;
case dcmdDoIt:
HandleDcmdDoIt(paramPtr);
break;
}
}
//====================================================================================================
//
// Routine: HandleDcmdInit
//
// Description: Handle a dcmdInit call
//
// Parameters: paramPtr - pointer to dcmd paramter block
//
// Returns: nothing
//
//====================================================================================================
static void
HandleDcmdInit(dcmdBlock *paramPtr)
{
#pragma unused (paramPtr)
long response;
GDHandle mainDeviceH;
Rect * gdRect;
short hOffset;
short vOffset;
gIsPowerPC = ((Gestalt(gestaltSysArchitecture, &response) == noErr) && (response == gestaltPowerPC));
gCivicRefNum = GetDriverRefNum("\p.Display_Video_Apple_Civic");
gHasCivic = (gCivicRefNum != 0);
gHasValkyrie = false; // to be added
gHasTVTuner = false; // to be added
gPlaythroughOn = false;
if (gHasCivic)
{
if (gIsPowerPC)
{
gCivicBaseAddr = (Ptr) kCivicPPCBaseAddr;
gSebasAddrReg = (Ptr) kSebasPPCAddrReg;
gSebasDataReg = (Ptr) kSebasPPCDataReg;
gSebasCLUT = (Ptr) kSebasPPCCLUT;
}
else
{
gCivicBaseAddr = (Ptr) kCivic68KBaseAddr;
gSebasAddrReg = (Ptr) kSebas68KAddrReg;
gSebasDataReg = (Ptr) kSebas68KDataReg;
gSebasCLUT = (Ptr) kSebas68KCLUT;
}
}
mainDeviceH = LMGetMainDevice(); // get handle to main screen device
gdRect = &(**mainDeviceH).gdRect;
hOffset = ((gdRect->right - gdRect->left) - kMacsBugMaxWidth) / 2;
if (hOffset < 0) hOffset = 0;
vOffset = ((gdRect->bottom - gdRect->top) - kMacsBugMaxHeight) / 2;
if (vOffset < 0) vOffset = 0;
gVideoRect.top = gdRect->top + vOffset;
gVideoRect.left = gdRect->right - hOffset - kDefaultVideoWidth;
gVideoRect.bottom = gVideoRect.top + kDefaultVideoHeight;
gVideoRect.right = gVideoRect.left + kDefaultVideoWidth;
}
//====================================================================================================
//
// Routine: HandleDcmdSecondaryInit
//
// Description: Handle a dcmdSecondaryInit call (new with format 3 dcmds)
//
// Parameters: paramPtr - pointer to dcmd paramter block
//
// Returns: nothing
//
//====================================================================================================
static void
HandleDcmdSecondaryInit(dcmdBlock *paramPtr)
{
#pragma unused (paramPtr)
}
//====================================================================================================
//
// Routine: HandleDcmdShutdown
//
// Description: Handle a dcmdShutdown call (new with format 3 dcmds)
//
// Parameters: paramPtr - pointer to dcmd paramter block
//
// Returns: nothing
//
//====================================================================================================
static void
HandleDcmdShutdown(dcmdBlock *paramPtr)
{
#pragma unused (paramPtr)
}
//====================================================================================================
//
// Routine: HandleDcmdHelp
//
// Description: Handle a dcmdHelp call
//
// Parameters: paramPtr - pointer to dcmd paramter block
//
// Returns: nothing
//
//====================================================================================================
static void
HandleDcmdHelp(dcmdBlock *paramPtr)
{
#pragma unused (paramPtr)
#if !Version3dcmd
dcmdDrawLine("\p" kDcmdNameStr " " kDcmdUsageStr);
dcmdDrawLine("\p The MacsBug TV dcmd - for Quadra and Power Macintosh AVs");
#endif
dcmdDrawLine("\p Options:");
dcmdDrawLine("\p on - turn video input on");
dcmdDrawLine("\p off - turn video input off");
dcmdDrawLine("\p s[ize] n - set video size [1/2/4 for full/half/quarter size]");
dcmdDrawLine("\p t[op] n - set video top coordinate");
dcmdDrawLine("\p l[eft] n - set video left coordinate");
dcmdDrawLine("\p w[idth] n - set video width");
dcmdDrawLine("\p h[eight] n - set video height");
if (gHasTVTuner)
dcmdDrawLine("\p ch[annel] n - select TV channel n");
#if !Version3dcmd
dcmdDrawLine("\p (" kDcmdCreditsStr ")");
#endif
}
//====================================================================================================
//
// Routine: HandleDcmdGetInfo
//
// Description: Handle a dcmdGetInfo call (new with format 3 dcmds)
//
// Parameters: paramPtr - pointer to dcmd paramter block
//
// Returns: nothing
//
//====================================================================================================
static void
HandleDcmdGetInfo(dcmdBlock *paramPtr)
{
#if !Version3dcmd
#pragma unused (paramPtr)
#else
dcmdFillVersion(paramPtr, kDcmdVersion);
dcmdFillString(paramPtr, usageStr, "\p" kDcmdUsageStr);
dcmdFillString(paramPtr, creditsStr, "\p" kDcmdCreditsStr);
#endif
}
//====================================================================================================
//
// Routine: HandleDcmdDoIt
//
// Description: Handle a dcmdDoIt call
//
// Parameters: paramPtr - pointer to dcmd paramter block
//
// Returns: nothing
//
//====================================================================================================
#define CR 0x0D
static void
HandleDcmdDoIt(dcmdBlock *paramPtr)
{
#pragma unused (paramPtr)
Boolean ok;
short delim;
long value;
Str255 option;
OSErr err = noErr;
dcmdSwapWorlds();
do
{
delim = dcmdGetNextParameter(option);
if (PLstrcmp(option, "\pon") == 0)
{
err = TurnVideoOn();
if (err == noErr)
dcmdDrawLine("\pVideo turned on");
else
dcmdDrawLine("\pUnable to turn video on");
}
else if (PLstrcmp(option, "\poff") == 0)
{
err = TurnVideoOff();
if (err == noErr)
dcmdDrawLine("\pVideo turned off");
else
dcmdDrawLine("\pUnable to turn video off");
}
else if ((PLstrcmp(option, "\pt") == 0) || (PLstrcmp(option, "\ptop") == 0))
{
delim = dcmdGetNextExpression(&value, &ok);
if (ok)
{
err = SetVideoTop(value);
if (err == noErr)
{
PutPStr("\pVideo top coordinate changed to ");
PutUDec(value);
}
else
PutPStr("\pUnable to change video top coordinate");
PutLine();
}
else
{
err = errMTVSyntaxError;
dcmdDrawLine("\pSyntax error");
}
}
else if ((PLstrcmp(option, "\pl") == 0) || (PLstrcmp(option, "\pleft") == 0))
{
delim = dcmdGetNextExpression(&value, &ok);
if (ok)
{
err = SetVideoLeft(value);
if (err == noErr)
{
PutPStr("\pVideo left coordinate changed to ");
PutUDec(value);
}
else
PutPStr("\pUnable to change video left coordinate");
PutLine();
}
else
{
err = errMTVSyntaxError;
dcmdDrawLine("\pSyntax error");
}
}
else if ((PLstrcmp(option, "\ps") == 0) || (PLstrcmp(option, "\psize") == 0))
{
delim = dcmdGetNextExpression(&value, &ok);
if (ok)
{
err = SetVideoSize(value);
if (err == noErr)
{
PutPStr("\pVideo size changed to ");
switch (value)
{
case 1: PutPStr("\pfull"); break;
case 2: PutPStr("\phalf"); break;
case 3: PutPStr("\pthird"); break;
case 4: PutPStr("\pquarter"); break;
}
}
else
PutPStr("\pUnable to change video size");
PutLine();
}
else
{
err = errMTVSyntaxError;
dcmdDrawLine("\pSyntax error");
}
}
else if ((PLstrcmp(option, "\pw") == 0) || (PLstrcmp(option, "\pwidth") == 0))
{
delim = dcmdGetNextExpression(&value, &ok);
if (ok)
{
err = SetVideoWidth(value);
if (err == noErr)
{
PutPStr("\pVideo width changed to ");
PutUDec(value);
}
else
PutPStr("\pUnable to change video width");
PutLine();
}
else
{
err = errMTVSyntaxError;
dcmdDrawLine("\pSyntax error");
}
}
else if ((PLstrcmp(option, "\ph") == 0) || (PLstrcmp(option, "\pheight") == 0))
{
delim = dcmdGetNextExpression(&value, &ok);
if (ok)
{
err = SetVideoHeight(value);
if (err == noErr)
{
PutPStr("\pVideo height changed to ");
PutUDec(value);
}
else
PutPStr("\pUnable to change video height");
PutLine();
}
else
{
err = errMTVSyntaxError;
dcmdDrawLine("\pSyntax error");
}
}
else if ((PLstrcmp(option, "\pch") == 0) || (PLstrcmp(option, "\pchannel") == 0))
{
delim = dcmdGetNextExpression(&value, &ok);
if (ok)
{
err = SetTVChannel(value);
if (err == noErr)
{
PutPStr("\pChannel changed to ");
PutUDec(value);
PutLine();
}
else if (err == errMTVHardwareNotAvailable)
dcmdDrawLine("\pTV tuner not present");
else
dcmdDrawLine("\pUnable to set channel");
}
else
{
err = errMTVSyntaxError;
dcmdDrawLine("\pSyntax error");
}
}
else if (PLstrcmp(option, "\pdc") == 0)
{
err = DumpCLUT();
}
else
{
err = errMTVUnknownOption;
dcmdDrawLine("\pUnknown option");
}
} while ((err == noErr) && (delim != CR));
dcmdSwapWorlds();
}
//====================================================================================================
//
// Routine: TurnVideoOn
//
// Description: Turn on the video
//
// Parameters: none
//
// Returns: error result code (negative) or noErr
//
//====================================================================================================
static OSErr
TurnVideoOn()
{
OSErr err;
CLUTEntry entry;
if (gHasCivic)
{
SetVideoPlaythrough(false); // disable playthrough
ReadCivicCLUTEntry(0x7F, &entry); // select entry 0x7F (background color) as key color
entry.alpha = 0xFF;
WriteCivicCLUTEntry(0x7F, &entry);
ReadCivicCLUTEntry(0xFF, &entry); // select entry 0xFF (foreground color) as key color
entry.alpha = 0xFF;
WriteCivicCLUTEntry(0xFF, &entry);
err = SetVideoRectangle(&gVideoRect); // set the playthough rectangle
SetVideoPlaythrough(true); // turn playthrough on
gPlaythroughOn = true;
return err;
}
else
return errMTVFeatureNotImplemented; // we only work on Civic for now
}
//====================================================================================================
//
// Routine: TurnVideoOff
//
// Description: Turn off the video
//
// Parameters: none
//
// Returns: error result code (negative) or noErr
//
//====================================================================================================
static OSErr
TurnVideoOff()
{
if (gHasCivic)
{
SetVideoPlaythrough(false); // disable playthrough
gPlaythroughOn = false; // remember that playthrough is off
return noErr;
}
else
return errMTVFeatureNotImplemented; // we only work on Civic for now
}
//====================================================================================================
//
// Routine: SetVideoSize
//
// Description: Set the size of the video playthrough area
//
// Parameters: size - 1, 2, 3 or 4 for full, half, third or quarter size
//
// Returns: error result code (negative) or noErr
//
//====================================================================================================
static OSErr
SetVideoSize(long size)
{
Rect newVideoRect;
if ((size == 1) || (size == 2) || (size == 4))
{
newVideoRect = gVideoRect;
newVideoRect.left = newVideoRect.right - (short) kMaximumVideoWidth / size;
newVideoRect.bottom = newVideoRect.top + (short) kMaximumVideoHeight / size;
return SetVideoRectangle(&newVideoRect);
}
else
return errMTVValueOutOfRange;
}
//====================================================================================================
//
// Routine: SetVideoLeft
//
// Description: Set the left coordinate of the video playthrough area
//
// Parameters: left - desired left of video area
//
// Returns: error result code (negative) or noErr
//
//====================================================================================================
static OSErr
SetVideoLeft(long left)
{
Rect newVideoRect;
if (left >= 0)
{
newVideoRect.top = gVideoRect.top;
newVideoRect.left = left;
newVideoRect.bottom = gVideoRect.bottom;
newVideoRect.right = left + (short) (gVideoRect.right - gVideoRect.left);
return SetVideoRectangle(&newVideoRect);
}
else
return errMTVValueOutOfRange;
}
//====================================================================================================
//
// Routine: SetVideoTop
//
// Description: Set the top coordinate of the video playthrough area
//
// Parameters: top - desired top of video area
//
// Returns: error result code (negative) or noErr
//
//====================================================================================================
static OSErr
SetVideoTop(long top)
{
Rect newVideoRect;
if (top >= 0)
{
newVideoRect.top = top;
newVideoRect.left = gVideoRect.left;
newVideoRect.bottom = top + (short) (gVideoRect.bottom - gVideoRect.top);
newVideoRect.right = gVideoRect.right;
return SetVideoRectangle(&newVideoRect);
}
else
return errMTVValueOutOfRange;
}
//====================================================================================================
//
// Routine: SetVideoWidth
//
// Description: Set the width of the video playthrough area
//
// Parameters: width - desired width of video area
//
// Returns: error result code (negative) or noErr
//
//====================================================================================================
static OSErr
SetVideoWidth(long width)
{
Rect newVideoRect;
if ((width >= kMinimumVideoWidth) && (width <= kMaximumVideoWidth))
{
newVideoRect = gVideoRect;
newVideoRect.left = newVideoRect.right - (short) width;
return SetVideoRectangle(&newVideoRect);
}
else
return errMTVValueOutOfRange;
}
//====================================================================================================
//
// Routine: SetVideoHeight
//
// Description: Set the width of the video playthrough area
//
// Parameters: width - desired width of video area
//
// Returns: error result code (negative) or noErr
//
//====================================================================================================
static OSErr
SetVideoHeight(long height)
{
Rect newVideoRect;
if ((height >= kMinimumVideoHeight) && (height <= kMaximumVideoHeight))
{
newVideoRect = gVideoRect;
newVideoRect.bottom = newVideoRect.top + (short) height;
return SetVideoRectangle(&newVideoRect);
}
else
return errMTVValueOutOfRange;
}
//====================================================================================================
//
// Routine: SetVideoPlaythrough
//
// Description: Turn video playthrough on or off
//
// Parameters: on - true to enable playthrough, false to disable playthrough
//
// Returns: error result code (negative) or noErr
//
//====================================================================================================
static void
SetVideoPlaythrough(Boolean on)
{
if (gHasCivic)
{
if (on)
{
*gSebasCLUT |= 0x80; // enable playthrough
NOP();
*(long *)(gCivicBaseAddr + 0x18) = 0; // unfreeze video
NOP();
}
else
{
*(long *)(gCivicBaseAddr + 0x18) = 1; // freeze video
NOP();
*gSebasCLUT &= 0x7F; // disable playthrough
NOP();
}
}
}
//====================================================================================================
//
// Routine: SetVideoRectangle
//
// Description: Set the video playthrough area
//
// Parameters: videoRect - pointer to desired playthrough rectangle
//
// Returns: error result code (negative) or noErr
//
//====================================================================================================
static OSErr
SetVideoRectangle(const Rect *videoRect)
{
GDHandle mainDeviceH;
VDVidInRect vidInRect;
CntrlParam pb;
OSErr err;
OSErr saveMemErr;
if (gHasCivic)
{
mainDeviceH = LMGetMainDevice(); // get handle to main screen device
if ((**mainDeviceH).gdRefNum == gCivicRefNum) // make sure main device is controlled by Civic
{
SetVideoPlaythrough(false); // disable playthrough
pb.csCode = csCivicSetVidInRect; // specify playthrough rectangle
pb.ioCRefNum = gCivicRefNum;
vidInRect.csPage = 0;
vidInRect.csBaseAddr = 0x98765432;
vidInRect.csRect.top = videoRect->top;
vidInRect.csRect.left = videoRect->left;
vidInRect.csRect.bottom = videoRect->bottom;
vidInRect.csRect.right = videoRect->right;
*(VDVidInRect **)&pb.csParam[0] = &vidInRect;
saveMemErr = LMGetMemErr(); // save value of MemErr since video driver is handle-based
err = PBControlImmed((ParmBlkPtr) &pb); // call Civic video driver to set playthough rectangle
LMSetMemErr(saveMemErr); // restore value of MemErr since PBControl trashed it
if (err == noErr)
gVideoRect = *videoRect; // update current rectangle
if (gPlaythroughOn)
SetVideoPlaythrough(true); // reenable playthrough
}
else
err = errMTVHardwareNotAvailable;
return err;
}
else
return errMTVFeatureNotImplemented; // we only work on Civic for now
}
//====================================================================================================
//
// Routine: ReadCivicCLUTEntry
//
// Description: Read an entry in the Civic CLUT
//
// Parameters: index - CLUT index (0x00..0xFF)
// entry - pointer to CLUT entry to be returned
//
// Returns: nothing
//
//====================================================================================================
static void
ReadCivicCLUTEntry(unsigned char index, CLUTEntryPtr entry)
{
*gSebasAddrReg = index;
NOP();
entry->red = *gSebasDataReg;
NOP();
entry->green = *gSebasDataReg;
NOP();
entry->blue = *gSebasDataReg;
NOP();
entry->alpha = *gSebasDataReg;
NOP();
}
//====================================================================================================
//
// Routine: WriteCivicCLUTEntry
//
// Description: Write an entry in the Civic CLUT
//
// Parameters: index - CLUT index (0x00..0xFF)
// entry - pointer to CLUT entry to write
//
// Returns: nothing
//
//====================================================================================================
static void
WriteCivicCLUTEntry(unsigned char index, const CLUTEntryPtr entry)
{
*gSebasAddrReg = index;
NOP();
*gSebasDataReg = entry->red;
NOP();
*gSebasDataReg = entry->green;
NOP();
*gSebasDataReg = entry->blue;
NOP();
*gSebasDataReg = entry->alpha;
NOP();
}
//====================================================================================================
//
// Routine: SetTVChannel
//
// Description: Set the television channel
//
// Parameters: channel - channel to select
//
// Returns: error result code (negative) or noErr
//
//====================================================================================================
#define kFirstChannel 2
#define kNumChannels 68
static OSErr
SetTVChannel(long channel)
{
static const long channelFreq[kNumChannels] = // table of U.S. channel frequencies
{
0x034B0C50, 0x03A699D0, 0x04022750, 0x049ABDD0,
0x04F64B50, 0x0A721A50, 0x0ACDA7D0, 0x0B293550,
0x0B84C2D0, 0x0BE05050, 0x0C3BDDD0, 0x0C976B50,
0x1C16B450, 0x1C7241D0, 0x1CCDCF50, 0x1D295CD0,
0x1D84EA50, 0x1DE077D0, 0x1E3C0550, 0x1E9792D0,
0x1EF32050, 0x1F4EADD0, 0x1FAA3B50, 0x2005C8D0,
0x20615650, 0x20BCE3D0, 0x21187150, 0x2173FED0,
0x21CF8C50, 0x222B19D0, 0x2286A750, 0x22E234D0,
0x233DC250, 0x23994FD0, 0x23F4DD50, 0x24506AD0,
0x24ABF850, 0x250785D0, 0x25631350, 0x25BEA0D0,
0x261A2E50, 0x2675BBD0, 0x26D14950, 0x272CD6D0,
0x27886450, 0x27E3F1D0, 0x283F7F50, 0x289B0CD0,
0x28F69A50, 0x295227D0, 0x29ADB550, 0x2A0942D0,
0x2A64D050, 0x2AC05DD0, 0x2B1BEB50, 0x2B7778D0,
0x2BD30650, 0x2C2E93D0, 0x2C8A2150, 0x2CE5AED0,
0x2D413C50, 0x2D9CC9D0, 0x2DF85750, 0x2E53E4D0,
0x2EAF7250, 0x2F0AFFD0, 0x2F668D50, 0x2FC21AD0
};
if (gHasTVTuner)
{
if ((channel >= kFirstChannel) && (channel <= kFirstChannel + kNumChannels - 1))
{
return errMTVFeatureNotImplemented;
}
else
return errMTVValueOutOfRange;
}
else
return errMTVHardwareNotAvailable;
}
//====================================================================================================
//
// Routine: DumpCLUT
//
// Description: Dump the video hardware CLUT to MacsBug
//
// Parameters: none
//
// Returns: error result code (negative) or noErr
//
//====================================================================================================
static OSErr
DumpCLUT()
{
CLUTEntry entry;
unsigned short index;
if (gHasCivic)
{
dcmdDrawLine("\pDisplaying Civic CLUT");
for (index = 0x00; index <= 0xFF; ++index)
{
ReadCivicCLUTEntry(index, &entry);
PutPStr("\p Entry ");
PutUHexZ(index, 2); PutPStr("\p: (");
PutUHexZ(entry.red, 2); PutPStr("\p, ");
PutUHexZ(entry.green, 2); PutPStr("\p, ");
PutUHexZ(entry.blue, 2); PutPStr("\p, ");
PutUHexZ(entry.alpha, 2); PutPStr("\p)");
PutLine();
}
return noErr;
}
else
{
dcmdDrawLine("\pUnable to dump CLUT");
return errMTVFeatureNotImplemented; // we only work on Civic for now
}
}
//====================================================================================================
//
// Routine: GetDriverRefNum
//
// Description: Find the refnum of the driver with the given name
//
// Parameters: driverName - name of desired driver
//
// Returns: driver refnum or 0 if not found
//
//====================================================================================================
static short
GetDriverRefNum(const StringPtr driverName)
{
DCtlHandle dceH;
DCtlHandle * unitTableBase = (DCtlHandle *) LMGetUTableBase();
DRVRHeaderPtr driverHdrP;
unsigned short unitTableEntries = LMGetUnitTableEntryCount();
unsigned short unitNum;
for (unitNum = 0; unitNum < unitTableEntries; ++unitNum)
{
dceH = unitTableBase[unitNum];
if (dceH != nil)
{
if ((**dceH).dCtlFlags & dRAMBasedMask)
driverHdrP = (DRVRHeaderPtr) (*(Handle)((**dceH).dCtlDriver));
else
driverHdrP = (DRVRHeaderPtr) ((**dceH).dCtlDriver);
if (EqualString(driverName, driverHdrP->drvrName, false, false))
return ~unitNum;
}
}
return 0;
}